package com.iflytek.jobs.service.service.impl;

import com.iflytek.jobs.service.domain.vo.AllFollowRecordPojo;
import com.iflytek.jobs.service.domain.vo.FollowInfoExcel;
import com.iflytek.jobs.service.domain.vo.FollowRecordImportDTO;
import com.iflytek.jobs.service.domain.vo.FollowRecordPojo;
import com.iflytek.jobs.service.mapper.FollowRecordMapper;
import com.iflytek.jobs.service.service.IFollowRecordService;
import com.iflytek.jobs.service.util.DateUtils;
import com.ruoyi.common.utils.SecurityUtils;
import com.ruoyi.common.utils.bean.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.time.LocalDateTime;
import java.time.format.DateTimeParseException;
import java.util.ArrayList;
import java.util.List;
import java.util.stream.Collectors;


@Service
public class FollowRecordServiceImpl implements IFollowRecordService {
    @Autowired
    private FollowRecordMapper followRecordMapper;

    /**
     * 根据账号查询学生
     * @param account 账号
     * @return 学生
     */
    @Override
    public List<String> queryStudent(String account){
        return followRecordMapper.queryStudentMapper(account);
    }

    /**
     * 添加回访记录
     * @param followRecordPojo 回访记录对象
     * @return true成功/false失败
     */
    @Override
    public boolean addFollowRecord(FollowRecordPojo followRecordPojo) {
        int result=followRecordMapper.addFollowRecord(followRecordPojo);
        return result > 0;
    }

    /**
     * 获取当前老师的所有回访记录
     * @param followRecordPojo 老师账号
     * @return 回访记录列表
     */
    @Override
    public List<AllFollowRecordPojo> queryAllFollowRecord(FollowRecordPojo followRecordPojo) {
        return followRecordMapper.queryAllFollowRecord(followRecordPojo);
    }

    /**
     * 获取指定学生的回访记录详细数据
     * @param followRecordPojo 学生信息
     * @return 回访记录列表
     */
    @Override
    public List<FollowRecordPojo> getDetailData(FollowRecordPojo followRecordPojo) {
        return  followRecordMapper.getDetailData(followRecordPojo);
    }

    /**
     * 获取编辑回访记录数据
     * @param followRecordPojo 回访记录对象
     * @return 回访记录对象
     */
    @Override
    public List<FollowRecordPojo> getEditData(FollowRecordPojo followRecordPojo) {
        return followRecordMapper.getEditData(followRecordPojo);
    }


    /**
     * 保存修改
     * @param followRecordPojo 回访记录对象
     * @return true成功/false失败
     */
    @Override
    public boolean saveChanges(FollowRecordPojo followRecordPojo) {
        int result=followRecordMapper.saveChanges(followRecordPojo);
        return result > 0;
    }

    /**
     * 查询是否有重复记录
     * @param followRecordPojo 回访记录对象
     * @return true无重复/false有重复
     */
    @Override
    public boolean repeatFollow(FollowRecordPojo followRecordPojo) {
        return followRecordMapper.repeatFollow(followRecordPojo) <= 0;
    }


    /**
     * 删除一条记录
     * @param followRecordPojo 回访记录对象
     * @return true成功/false失败
     */
    @Override
    public boolean deleteRecord(FollowRecordPojo followRecordPojo) {
        return followRecordMapper.deleteRecord(followRecordPojo) > 0;
    }

    /**
     * 获取比较记录
     * @param followRecordPojo 回访记录对象
     * @return  回访记录对象
     */
    @Override
    public FollowRecordPojo compareRecord(FollowRecordPojo followRecordPojo) {

        return followRecordMapper.compareRecord(followRecordPojo);
    }


    /**
     * 导出数据到excel
     * @param followRecordPojo 回访记录对象
     * @return 回访记录列表
     */
    @Override
    public List<FollowInfoExcel> excelFollowRecord(FollowRecordPojo followRecordPojo) {
        List<FollowRecordPojo> followRecordPojoList = followRecordMapper.excelFollowRecord(followRecordPojo);
        List<FollowInfoExcel> followInfoExcelList = new ArrayList<>();
        if(followRecordPojoList!=null && !followRecordPojoList.isEmpty()){
            for (FollowRecordPojo record : followRecordPojoList){
                FollowInfoExcel followInfoExcel = new FollowInfoExcel();
                followInfoExcel.setStreetAddress(record.getStreetAddress());
                followInfoExcel.setNickName(record.getNickName());
                followInfoExcel.setVisitTime(record.getVisitTime().toString());
                followInfoExcel.setGrade(record.getGrade());
                followInfoExcel.setMajor(record.getMajor());
                followInfoExcel.setVisitCount(record.getVisitCount().toString());
                if (record.getInternStatus()==1){
                    followInfoExcel.setInternStatus("实习中");
                }else if(record.getInternStatus()==0){
                    followInfoExcel.setInternStatus("实习中");
                }else {
                    followInfoExcel.setInternStatus(" ");
                }
                followInfoExcel.setCompany(record.getCompany());
                followInfoExcel.setPosition(record.getPosition());
                followInfoExcel.setSalary(record.getSalary().toString());
                followInfoExcel.setRegion(record.getRegion());
                followInfoExcel.setStreetAddress(record.getStreetAddress());
                if (record.getHasChangedIntern()==1){
                            followInfoExcel.setHasChangedIntern("换过");
                }else if(record.getHasChangedIntern()==0){
                    followInfoExcel.setHasChangedIntern("未换过");
                }else {
                    followInfoExcel.setHasChangedIntern(" ");
                }
                followInfoExcel.setChangedCount(record.getChangedCount());
                if (record.getIsMajorMatched()==1){
                    followInfoExcel.setIsMajorMatched("对口");
                }else if(record.getIsMajorMatched()==0){
                    followInfoExcel.setIsMajorMatched("不对口");
                }else {
                    followInfoExcel.setIsMajorMatched(" ");
                }
                if (record.getPlanToChange()==1){
                    followInfoExcel.setPlanToChange("不打算换");
                }else if(record.getPlanToChange()==0){
                    followInfoExcel.setPlanToChange("打算换");
                }else {
                    followInfoExcel.setPlanToChange(" ");
                }
                followInfoExcel.setIdealCity(record.getIdealCity());
                followInfoExcel.setIdealSalary(record.getIdealSalary().toString());
                followInfoExcel.setIdealPosition(record.getIdealPosition());
                followInfoExcel.setStudentIdeas(record.getStudentIdeas());
                followInfoExcel.setTeacherGuidance(record.getTeacherGuidance());
                followInfoExcel.setStudentAccount(record.getStudentAccount());
                followInfoExcelList.add(followInfoExcel);
            }
            return followInfoExcelList;
        }
        return null;
    }

    /**
     * excel导入数据
     */
    @Override
    public void batchImportFollowRecord(List<FollowRecordImportDTO> importList) {
        System.out.println();
        // DTO 转换为数据库实体类，处理所有特殊逻辑
        List<FollowRecordPojo> recordList = importList.stream()
                .map(this::convertToPojo)
                .collect(Collectors.toList());
        // 批量插入数据库（需确保 Mapper 批量插入方法正确）
        if (!recordList.isEmpty()) {
            followRecordMapper.batchInsert(recordList);
        }
    }

    /**
     * DTO 转 实体类核心逻辑
     * 解决字段类型差异、格式转换、数据校验问题
     */
    private FollowRecordPojo convertToPojo(FollowRecordImportDTO dto) {
        FollowRecordPojo pojo = new FollowRecordPojo();
        // 复制字段名一致且类型匹配的属性
        BeanUtils.copyProperties(dto, pojo);

        // 1. 处理日期类型转换：String (Excel) → LocalDateTime (实体类)
        try {
            pojo.setVisitTime(LocalDateTime.parse(dto.getVisitTime(), DateUtils.FORMATTER));
        } catch (DateTimeParseException e) {
            throw new RuntimeException("回访时间格式错误，正确格式：yyyy-MM-dd HH:mm:ss，数据：" + dto.getVisitTime());
        }

        // 2. 处理年级转换：Integer (DTO) → String (实体类) + 范围校验（符合数据库约束）
        if (dto.getGrade() == null || dto.getGrade() < 2000 || dto.getGrade() > 2500) {
            throw new RuntimeException("年级格式错误，需为2000-2500之间的整数，数据：" + dto.getGrade());
        }
        pojo.setGrade(String.valueOf(dto.getGrade()));

        // 3. 处理薪资转换：String (Excel，支持纯数字/带元) → Integer (实体类)
        pojo.setSalary(convertSalaryToInteger(dto.getSalary()));
        // 理想薪资同理转换
        pojo.setIdealSalary(convertSalaryToInteger(dto.getIdealSalary()));

        // 4. 状态字段校验与类型转换（确保符合数据库 0/1 约束）
        validateAndSetStatus(dto.getInternStatus(), pojo::setInternStatus, "实习状态");
        validateAndSetStatus(dto.getHasChangedIntern(), pojo::setHasChangedIntern, "是否换过实习");
        validateAndSetStatus(dto.getIsMajorMatched(), pojo::setIsMajorMatched, "是否专业对口");
        validateAndSetStatus(dto.getPlanToChange(), pojo::setPlanToChange, "是否打算换实习");

        // 5. 满意度校验（数据库1-5分，实体类1-10分，兼容处理）
        if (dto.getSatisfaction() != null) {
            if (dto.getSatisfaction() < 1 || dto.getSatisfaction() > 5) {
                throw new RuntimeException("满意度格式错误，需为1-5分，数据：" + dto.getSatisfaction());
            }
            pojo.setSatisfaction(dto.getSatisfaction());
        }

        // 6. 字段映射修正：DTO换岗次数 → 实体类换岗次数（字段名差异）
        pojo.setChangedCount(dto.getChangeCount() != null ? dto.getChangeCount() : 0);

        // 7. 填充缺失的必填字段（数据库非空约束）
        // 7.1 教师账号：从当前登录上下文获取（若依框架默认提供）
        pojo.setTeacherAccount(SecurityUtils.getUsername());
        // 7.2 学生昵称：用Excel中的学生姓名填充
        pojo.setNickName(dto.getNickName());
        // 7.3 创建/更新时间：手动设置（数据库可自动维护，此处双重保障）
        String now = LocalDateTime.now().format(DateUtils.FORMATTER);
        pojo.setCreateTime(now);
        pojo.setUpdateTime(now);

        // 8. 非必填字段空值处理（避免数据库字段类型不匹配）
        if (pojo.getChangedCount() == 0 && dto.getChangeCount() == null) {
            pojo.setChangedCount(0); // 未换过实习时默认0次
        }
        // 教师账号
        String teacherAccount = SecurityUtils.getUsername();
        pojo.setTeacherAccount(teacherAccount);
        return pojo;
    }

    /**
     * 薪资转换工具：String → Integer（支持纯数字、带"元"字符）
     */
    private Integer convertSalaryToInteger(String salaryStr) {
        if (salaryStr == null || salaryStr.trim().isEmpty()) {
            return null;
        }
        // 去除所有非数字字符（保留整数部分）
        String cleanStr = salaryStr.replaceAll("[^0-9]", "");
        if (cleanStr.isEmpty()) {
            throw new RuntimeException("薪资格式错误，需为数字或带元的数字，数据：" + salaryStr);
        }
        return Integer.parseInt(cleanStr);
    }

    /**
     * 状态字段校验与设置（确保值为0或1，适配实体类int类型）
     */
    private void validateAndSetStatus(Integer status, java.util.function.IntConsumer setter, String fieldName) {
        if (status == null) {
            return; // 非必填字段，空值不处理
        }
        if (status != 0 && status != 1) {
            throw new RuntimeException(fieldName + "格式错误，需为0或1，数据：" + status);
        }
        setter.accept(status); // 设值到实体类
    }
}
